#include "oqs_prov.h"
#include "test_common.h"
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <openssl/core_dispatch.h>
#include <openssl/core_names.h>
#include <openssl/provider.h>
#include <openssl/ssl.h>
#include <openssl/pem.h>
#include <openssl/x509.h>
#include <openssl/x509v3.h>
#include <openssl/trace.h>
#include <openssl/params.h>
#include <openssl/err.h>
#include <openssl/evp.h>
#include <openssl/param_build.h>
#include <openssl/bio.h> 
#include <openssl/asn1.h>
#include <openssl/ec.h>
#include <openssl/rsa.h>
#include <errno.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <time.h> 
const char *kHybridSignatureAlgorithms[] = {
    "p256_MLDSA44", "rsa3072_MLDSA44", "p384_MLDSA65", "p521_MLDSA87",
    "p256_falcon512", "rsa3072_falcon512", "p256_falconpadded512", "rsa3072_falconpadded512",
    "p521_falcon1024", "p521_falconpadded1024", "p256_sphincssha2128fsimple", "rsa3072_sphincssha2128fsimple",
    "p256_sphincssha2128ssimple", "rsa3072_sphincssha2128ssimple", "p384_sphincssha2192fsimple",
    "p256_sphincsshake128fsimple", "rsa3072_sphincsshake128fsimple", NULL
};

struct SigPair {
    unsigned char *sigma1;
    size_t sigma1_len;
    unsigned char *sigma2;
    size_t sigma2_len;
} signature;

         
static int nid = NID_undef; 

static OSSL_LIB_CTX *init_openssl(void);

void initialize_openssl_globals() ;

static int is_signature_algorithm_hybrid(const char **list, const char *s) ;

char *get_oqs_fromtls(const char *tlsname);

char *get_cls_fromtls(const char *tlsname) ;

static EVP_PKEY *generate_classic_evp(const char *classic_names);

static EVP_PKEY *generate_pq_evp(OSSL_LIB_CTX *libctx, const char *oqsname);

X509_REQ *generate_cert_req(EVP_PKEY *pkey);

static  int get_signature_data(X509_REQ *cert_req, EVP_PKEY *pkey);

X509 *generate_final_cert(X509_REQ *cert_req,EVP_PKEY *pkey);

static int write_privkey_to_file(const char *filename, EVP_PKEY *pkey) ;

static int write_x509_to_file(const char *filename, X509 *cert) ;

int create_hybrid_cert(OSSL_LIB_CTX *libctx,const char *signames,char * key_addr,char **certpath, char **classkeypath, char **oqskeypath);


